package de.op.projectc.screens;

import com.badlogic.gdx.Game;
import com.badlogic.gdx.Gdx;
import com.badlogic.gdx.Screen;
import com.badlogic.gdx.graphics.GL20;
import com.badlogic.gdx.graphics.Texture;
import com.badlogic.gdx.physics.box2d.Box2DDebugRenderer;
import com.badlogic.gdx.scenes.scene2d.Actor;
import com.badlogic.gdx.scenes.scene2d.InputEvent;
import com.badlogic.gdx.scenes.scene2d.InputListener;
import com.badlogic.gdx.scenes.scene2d.Stage;
import com.badlogic.gdx.scenes.scene2d.ui.*;
import com.badlogic.gdx.scenes.scene2d.utils.ChangeListener;
import com.badlogic.gdx.utils.viewport.ExtendViewport;
import de.op.projectc.MainGame;
import de.op.projectc.helper.CameraHelper;
import de.op.projectc.helper.WorldHelper;
import de.op.projectc.objects.Heli;
import de.op.projectc.objects.TerrainWorld;
import de.op.projectc.objects.TerrainWorld_old;
import de.op.projectc.stats.Options;
import de.op.projectc.stats.Score;

public class GameScreen implements Screen {
	final MainGame game;

    public enum GameState { READY, RUNNING, PAUSED, GAMEOVER }
    public static GameState gameState = GameState.READY;

    private Stage stage;
	private Skin skin;

	Label labelScore;
    Label labelCurrentHighScore;
	Label labelHighScore;
	Button button;
    Label labelFPS;

    Dialog pauseDialog;

    Heli heli;
    TerrainWorld terrainWorld;
    Box2DDebugRenderer debugRenderer = new Box2DDebugRenderer();
	
	public GameScreen(final MainGame game) {
		this.game = game;

        WorldHelper.getInstance();

        Texture texture = new Texture(Gdx.files.internal("heli.png"));

		heli = new Heli(texture,
                CameraHelper.getInstance().viewportWidth / 10,  CameraHelper.getInstance().viewportHeight / 10);

        terrainWorld = new TerrainWorld(heli);
        createUI();

        gameState = GameState.RUNNING;
	}

	private void createUI() {
		stage = new Stage(new ExtendViewport(Gdx.graphics.getWidth(), Gdx.graphics.getHeight()));
		skin = new Skin(Gdx.files.internal("ui/uiskin.json"));

		Table table = new Table(skin);
		table.setFillParent(true);
        table.setBounds(0, 0, stage.getWidth(), stage.getHeight());
        table.top();

		labelScore = new Label("Score: ", skin);
        labelCurrentHighScore = new Label("Best Score: ", skin);
		labelHighScore = new Label("Highscore: not yet implemented", skin);


		//ImageButton
        createPauseDialog();
		button = new TextButton("II", skin);
        button.addListener(new ChangeListener() {
            @Override
            public void changed(ChangeEvent event, Actor actor) {

                gameState = GameState.PAUSED;

                pauseDialog.show(stage);
            }
        });

		//labelScore.setFontScale(2);
        //labelCurrentHighScore.setFontScale(2);
		//labelHighScore.setFontScale(2);

		table.defaults().pad(5);
		table.add(labelScore).left().expandX();
        table.add(button).size(labelScore.getPrefHeight());
		table.add(labelCurrentHighScore).right().expandX();
        table.row();
        table.add(labelHighScore).left();

		table.debug();

        Table table2 = new Table(skin);
        table2.setFillParent(true);
        table2.bottom();

        labelFPS = new Label("FPS: ", skin);
        table2.add(labelFPS).left();

		stage.addActor(table);
        stage.addActor(table2);
    }

    private void createPauseDialog() {
        pauseDialog = new Dialog("PAUSE", skin) {

            protected void result (Object object) {
                switch((Integer) object) {
                    case 0:
                        gameState = GameState.RUNNING;
                        break;
                    case 1:
                        game.setScreen(new OptionScreen(game));
                        break;
                    case 2:
                        GameScreen.this.dispose();
                        game.setScreen(new MainMenuScreen(game));
                        break;
                    default:
                        gameState = GameState.RUNNING;
                        break;
                }
            }
        };

        pauseDialog.pad(70, 20,20, 20);

        pauseDialog.getContentTable().setScale(2);
        pauseDialog.getContentTable().defaults().pad(3);
        pauseDialog.getButtonTable().defaults().fillX().pad(3);
        pauseDialog.button("Zurueck zum Spiel", 0);
        pauseDialog.getButtonTable().row();
        pauseDialog.button("Optionen", 1).row();
        pauseDialog.getButtonTable().row();
        pauseDialog.button("Spiel beenden", 2).row();
    }

    @Override
	public void render(float delta) {
        switch (gameState) {
            case READY:
                break;
            case RUNNING:
                renderRunning(delta);
                break;
            case PAUSED:
                renderPaused(delta);
                renderRunning(0);
                break;
            case GAMEOVER:
                break;
        }

        renderUI(delta);
    }

    private void renderUI(float delta) {
        this.labelScore.setText("Score: " + Score.getInstance().getCurrentScore());
        this.labelCurrentHighScore.setText("Best Score: " + Score.getInstance().getCurrentHighScore());
        this.labelFPS.setText("FPS: " + Gdx.graphics.getFramesPerSecond());

        stage.act(delta);
        stage.draw();

        if(Options.getInstance().isDEBUG()) {
            debugRenderer.render(WorldHelper.getInstance(), CameraHelper.getInstance().combined);
            Table.drawDebug(stage);
        }
    }

    private void renderRunning(float delta) {
        Gdx.graphics.getGL20().glClearColor(0f, 0f, 0f, 1);
        Gdx.graphics.getGL20().glClear(GL20.GL_COLOR_BUFFER_BIT);

        //Gdx.graphics.getGL20().glEnable(GL20.GL_BLEND);
        //Gdx.graphics.getGL20().glBlendFunc(GL20.GL_ZERO, GL20.GL_SRC_COLOR);
        CameraHelper.getInstance().position.set(CameraHelper.getInstance().viewportWidth / 2,
                this.heli.getPositionY(), CameraHelper.getInstance().position.z);
        CameraHelper.getInstance().update();

        WorldHelper.getInstance().step(delta, 6, 4);

        terrainWorld.update(delta);
        terrainWorld.render(game.batch);

        heli.update(delta);

        game.batch.setProjectionMatrix(CameraHelper.getInstance().combined);
        game.batch.begin();
        heli.render(game.batch);
        game.batch.end();
    }

    //TODO durchstichtig grau zeichnen
    private void renderPaused(float delta) {

    }

    @Override
	public void dispose() {
        this.stage.dispose();
        this.skin.dispose();

        this.heli.dispose();
        this.terrainWorld.dispose();

        WorldHelper.dispose();
	}

	@Override
	public void hide() {
	}

	@Override
	public void pause() {
	}

	@Override
	public void resize(int width, int height) {
        stage.getViewport().update(width, height, true);
    }

	@Override
	public void resume() {
	}

	@Override
	public void show() {
        Gdx.input.setInputProcessor(stage);

        if(gameState == GameState.PAUSED) {
            pauseDialog.show(stage);
          //gameState = GameState.RUNNING;
        }
	}
}
